package com.laolang.pluto.framework.config.security.service;

import cn.hutool.core.util.StrUtil;
import com.laolang.pluto.common.util.LogUtil;
import com.laolang.pluto.framework.config.security.pojo.LoginUser;
import com.laolang.pluto.module.sys.consts.entity.SysTenantConst;
import com.laolang.pluto.module.sys.consts.entity.SysUserConst;
import com.laolang.pluto.module.sys.entity.SysTenant;
import com.laolang.pluto.module.sys.entity.SysUser;
import com.laolang.pluto.module.sys.service.SysTenantService;
import com.laolang.pluto.module.sys.service.SysUserService;
import java.util.HashSet;
import java.util.Set;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.stereotype.Service;

/**
 * @author laolang
 * @date 2021-08-07 00:11
 */
@Slf4j
@RequiredArgsConstructor
@Service
public class UserDetailsServiceImpl implements UserDetailsService {

    private final SysUserService sysUserService;
    private final SysTenantService sysTenantService;

    @Override
    public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
        SysUser sysUser = sysUserService.getByUsername(username);
        if (null == sysUser) {
            String logMsg = StrUtil.format("登录用户:[{}] 不存在", username);
            LogUtil.info(log, logMsg);
            throw new UsernameNotFoundException(logMsg);
        }

        // 账号是否被锁定
        if (SysUserConst.Status.LOCK.getValue() == sysUser.getStatus()) {
            LogUtil.info(log, StrUtil.format("登录用户:[{}] 被锁定", username));
            throw new UsernameNotFoundException(StrUtil.format("对不起, 您的账号:{} 被锁定, 请联系管理员", username));
        }

        // 租户是否被锁定
        SysTenant sysTenant = sysTenantService.getById(sysUser.getTenantId());
        if (null == sysTenant) {
            LogUtil.error(log, StrUtil.format("用户:{} 的租户不存在", username));
            throw new UsernameNotFoundException("租户不存在");
        }
        if (SysTenantConst.Status.LOCK.getValue() == sysTenant.getStatus()) {
            LogUtil.info(log, StrUtil.format("登录用户:[{}] 的租户:[id:{} name:{}]被被锁定", username, sysTenant.getId(),
                    sysTenant.getName()));
            throw new UsernameNotFoundException(StrUtil.format("对不起, 您的账号:{} 被锁定, 请联系管理员", username));
        }
        // TODO 添加菜单查询
        Set<String> menuList = new HashSet<>();
        menuList.add("*:*:*");
        return new LoginUser(sysUser, menuList);
    }
}
